﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Runtime.Serialization;
using System.IO;

namespace Genuilder.Extensibility
{
	[DataContract]
	public class GenItemHistory
	{
		[DataMember]
		public string Name
		{
			get;
			set;
		}
		[DataMember]
		public string SourceType
		{
			get;
			set;
		}
		[DataMember]
		public DateTime LastModified
		{
			get;
			set;
		}
		[DataMember]
		public bool Generated
		{
			get;
			set;
		}

		[DataMember]
		public String Parent
		{
			get;
			set;
		}
		[DataMember]
		public String ParentType
		{
			get;
			set;
		}

		internal static GenItemHistory CreateFrom(GenItem genItem)
		{
			return new GenItemHistory()
			{
				Name = genItem.Name,
				SourceType = genItem.SourceType.ToString(),
				LastModified = new FileInfo(genItem.Name).LastWriteTimeUtc,
				Generated = genItem.Generated,
				Parent = genItem.Parent == null ? null : genItem.Parent.Name,
				ParentType = genItem.Parent == null ? null : genItem.Parent.SourceType.ToString()
			};
		}

		internal GenItem ToSourceFile(ExecutionContext factory)
		{
			return factory.Create(new SourceFile(Name, (SourceType)Enum.Parse(typeof(SourceType), SourceType)), Generated);
		}
	}

	[DataContract]
	public class RunHistory
	{
		public RunHistory()
		{
			GenItems = new List<GenItemHistory>();
		}
		[DataMember]
		public List<GenItemHistory> GenItems
		{
			get;
			set;
		}
		public void Save(string path)
		{
			DataContractSerializer serializer = CreateSerializer();
			using(var fs = File.Open(path, FileMode.Create, FileAccess.Write))
			{
				serializer.WriteObject(fs, this);
			}
		}

		private static DataContractSerializer CreateSerializer()
		{
			return new DataContractSerializer(typeof(RunHistory));
		}
		public static RunHistory LoadOrNull(string file)
		{
			if(!File.Exists(file))
				return null;
			DataContractSerializer serializer = CreateSerializer();
			using(var fs = File.Open(file, FileMode.Open, FileAccess.Read))
			{
				return (RunHistory)serializer.ReadObject(fs);
			}
		}

		Dictionary<SourceFile, GenItemHistory> _HistoriesByName;
		internal GenItemHistory GetGenItemHistoryBySourceFile(SourceFile sourceFile)
		{
			if(_HistoriesByName == null)
			{
				_HistoriesByName = GenItems.ToDictionary(i => new SourceFile(i.Name, (SourceType)Enum.Parse(typeof(SourceType), i.SourceType)));
			}
			GenItemHistory result = null;
			_HistoriesByName.TryGetValue(sourceFile, out result);
			return result;
		}
	}
}
